package com.vietnam.power.service.impl;

import java.util.ArrayList;
import java.util.List;

import javax.mail.MessagingException;
import javax.mail.internet.MimeMessage;

import org.apache.commons.collections.CollectionUtils;
import org.apache.commons.lang.StringUtils;
import org.apache.log4j.Logger;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.mail.javamail.MimeMessageHelper;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Isolation;
import org.springframework.transaction.annotation.Propagation;
import org.springframework.transaction.annotation.Transactional;

import com.vietnam.power.admin.controller.MailController;
import com.vietnam.power.constant.AppConfigurationConstant;
import com.vietnam.power.constant.GeneralConstant;
import com.vietnam.power.dao.MessageDao;
import com.vietnam.power.domain.Article;
import com.vietnam.power.domain.ArticleSearchCriteria;
import com.vietnam.power.domain.MessageSearchCriteria;
import com.vietnam.power.persitence.EmailNotification;
import com.vietnam.power.persitence.MessageInfo;
import com.vietnam.power.persitence.MessageTypeDictionary;
import com.vietnam.power.service.ArticleService;
import com.vietnam.power.service.MailService;
import com.vietnam.power.service.MessageService;
import com.vietnam.power.util.DateTimeUtil;

@Service("messageInfo")
@Transactional(propagation = Propagation.REQUIRED, isolation = Isolation.READ_COMMITTED)
public class MessageServiceImpl implements MessageService {
	private static Logger logger = Logger.getLogger(MessageServiceImpl.class);
	@Autowired
	MessageDao messageDao;

	@Autowired
	private MailService mailService;

	@Autowired
	private ArticleService articleService;

	public void createMessage(com.vietnam.power.domain.MessageInfo mess) {
		// set status unread
		mess.setStatus(AppConfigurationConstant.MESSAGE.UNREAD);

		MessageInfo mi = new MessageInfo();
		mess.convertToPersist(mi);
		// set message type
		MessageTypeDictionary inbox = messageDao.getMessageTypeDictionary(AppConfigurationConstant.MESSAGE.INBOX);
		mi.setMessageTypeDictionary(inbox);
		inbox.addMessageInfo(mi);

		/*
		 * EmailNotification en = new EmailNotification();
		 * en.setNotifiedDate(DateTimeUtil
		 * .getCurrentDateByTimezone(GeneralConstant.VIET_NAM_TIMEZONE));
		 * en.setStatus(AppConfigurationConstant.MESSAGE.UNSENT);
		 * en.setMessageInfo(mi); mi.addEmailNotification(en);
		 */

		messageDao.createMessage(mi);
	}

	public void createEmail(com.vietnam.power.domain.MessageInfo mess) {
		// set status read
		mess.setStatus(AppConfigurationConstant.MESSAGE.READ);

		MessageInfo mi = new MessageInfo();
		mess.convertToPersist(mi);
		// set message type
		MessageTypeDictionary inbox = messageDao.getMessageTypeDictionary(AppConfigurationConstant.MESSAGE.SEND);
		mi.setMessageTypeDictionary(inbox);
		inbox.addMessageInfo(mi);

		EmailNotification en = new EmailNotification();
		en.setNotifiedDate(DateTimeUtil.getCurrentDateByTimezone(GeneralConstant.VIET_NAM_TIMEZONE));
		en.setStatus(AppConfigurationConstant.MESSAGE.UNSENT);
		en.setMessageInfo(mi);
		mi.addEmailNotification(en);

		messageDao.createMessage(mi);
	}
	
	public com.vietnam.power.domain.MessageInfo getMessageById(int id) {
		com.vietnam.power.domain.MessageInfo mi = new com.vietnam.power.domain.MessageInfo();

		MessageInfo pmi = messageDao.getMessageById(id);

		mi.convertToDomain(pmi);

		return mi;
	}

	public List<com.vietnam.power.domain.MessageInfo> searchMessages(MessageSearchCriteria tsc) {
		List<com.vietnam.power.domain.MessageInfo> lst = new ArrayList<com.vietnam.power.domain.MessageInfo>();
		ArticleSearchCriteria asc = new ArticleSearchCriteria();
		asc.setArticleGroupName(AppConfigurationConstant.ARTICLE_GROUP.CONTACT);
		List<Article> artList = articleService.getArticleListByGroupName(asc, null);
		if (CollectionUtils.isNotEmpty(artList)) {
			String email = artList.get(0).getEmail();
			tsc.setEmail(email);
			List<MessageInfo> pmis = messageDao.searchMessages(tsc);
			for (MessageInfo pmi : pmis) {
				com.vietnam.power.domain.MessageInfo mi = new com.vietnam.power.domain.MessageInfo();
				mi.convertToDomain(pmi);
				lst.add(mi);
			}
		}

		return lst;
	}

	public void deleteMessages(int id) {
		MessageInfo pmi = messageDao.getMessageById(id);
		messageDao.deleteMessage(pmi);
	}

	// move message to trash
	public void moveToTrash(int id) {
		MessageTypeDictionary inbox = messageDao.getMessageTypeDictionary(AppConfigurationConstant.MESSAGE.TRASH);
		MessageInfo pmi = messageDao.getMessageById(id);

		pmi.setMessageTypeDictionary(inbox);
		inbox.addMessageInfo(pmi);

		messageDao.updateMessage(pmi);
	}

	public void markMessageAsRead(int id) {
		MessageInfo pmi = messageDao.getMessageById(id);
		pmi.setStatus(AppConfigurationConstant.MESSAGE.READ);
		messageDao.updateMessage(pmi);
	}

	public void markMessageAsUnRead(int id) {
		MessageInfo pmi = messageDao.getMessageById(id);
		pmi.setStatus(AppConfigurationConstant.MESSAGE.UNREAD);
		messageDao.updateMessage(pmi);
	}

	public void sendEmail() {
		List<EmailNotification> emailNotifications = messageDao.getScheduledMessages();
		ArticleSearchCriteria asc = new ArticleSearchCriteria();
		asc.setArticleGroupName(AppConfigurationConstant.ARTICLE_GROUP.CONTACT);
		List<Article> artList = articleService.getArticleListByGroupName(asc, null);
		if (CollectionUtils.isNotEmpty(artList)) {
			String email = artList.get(0).getEmail();
			String password = artList.get(0).getPassword();
			for (EmailNotification emailNotification : emailNotifications) {
				try {
					MessageInfo currentMessage = emailNotification.getMessageInfo();
					MimeMessage message = mailService.createMimeMessage();

					MimeMessageHelper helper = new MimeMessageHelper(message, true, "UTF-8");

					helper.setFrom(currentMessage.getFrom());
					helper.setTo(currentMessage.getTo());
					if (StringUtils.isNotBlank(currentMessage.getCc())) {
						helper.setCc(currentMessage.getCc());
					}
					helper.setSubject(currentMessage.getSubject());
					helper.setText(currentMessage.getContent(), true);
					mailService.sendEmail(message, email, password);
					// update as sent already
					emailNotification.setStatus(AppConfigurationConstant.MESSAGE.SENT);
					messageDao.updateEmailNotification(emailNotification);
				} catch (MessagingException e) {
					logger.error(e);
				}
			}
		}
	}

	public void fetchEmail() throws Exception {
		ArticleSearchCriteria asc = new ArticleSearchCriteria();
		asc.setArticleGroupName(AppConfigurationConstant.ARTICLE_GROUP.CONTACT);
		List<Article> artList = articleService.getArticleListByGroupName(asc, null);
		if (CollectionUtils.isNotEmpty(artList)) {
			String email = artList.get(0).getEmail();
			String password = artList.get(0).getPassword();
			List<com.vietnam.power.domain.MessageInfo> infos = mailService.fetchEmail(email, password);
			
			for (com.vietnam.power.domain.MessageInfo mi:infos) {
				mi.setContent(mi.getContent().replace("\r\n", "<br/>"));
				this.createMessage(mi);
			}
		}
	}
}
